﻿
Public Module _interfaceOperations
    Private Function copyClone(Of valueT)(ByRef dest As valueT, ByVal src As valueT) As Boolean
        dest = DirectCast((DirectCast(src, ICloneable).Clone()), valueT)
        Return True
    End Function

    Public Function copy(Of valueT)(ByRef dest As valueT, ByVal src As valueT) As Boolean
        If isCloneable(src) Then
            Return copyClone(dest, src)
        Else
            Return eva(dest, src)
        End If
    End Function

    Public Function copy(Of T)(ByVal i As T) As T
        If i Is Nothing Then
            Return Nothing
        End If

        If isdebugmode() AndAlso Not isCloneable(i) Then
            raiseError("input is not cloneable, type " + GetType(T).FullName, errorHandle.errorType.exclamation)
        End If
        Dim rtn As T = Nothing
        copy(rtn, i)
        Return rtn
    End Function

    Public Function containsInterface(Of T)(ByVal interfaceName As String) As Boolean
        Dim i As T = Nothing
        i = alloc(Of T)()
        Return containsInterface(i, interfaceName)
    End Function

    Public Function containsInterface(Of T)(ByVal this As T, ByVal interfaceName As String) As Boolean
        If Not this Is Nothing Then
#If PocketPC OrElse Smartphone Then
            Dim i As System.Collections.IEnumerator = this.GetType.GetInterfaces.GetEnumerator()
            Dim found As Boolean = False
            While i.MoveNext
                If CType(i.Current, Type).Name = interfaceName Then
                    found = True
                    Exit While
                End If
            End While
            Return found
#Else
            Dim tp As Type = this.GetType().GetInterface(interfaceName, True)
            Return Not tp Is Nothing
#End If
        Else
            Return False
        End If
    End Function

    Public Function istype(Of T2, T)(ByVal this As T) As Boolean
        Return Not this Is Nothing AndAlso TypeOf this Is T2
    End Function

    Public Function istype(Of T)(ByVal this As Object) As Boolean
        Return istype(Of T, Object)(this)
    End Function

    Public Function isCloneable(Of T)(ByVal this As T) As Boolean
#If RETIRED Then
        Return containsInterface(this, "ICloneable")
        Return Not this Is Nothing AndAlso TypeOf this Is ICloneable
#End If
        Return istype(Of ICloneable, T)(this)
    End Function

    Public Function isCloneable(Of T)() As Boolean
        Dim this As T = Nothing
        this = alloc(Of T)()
        Return isCloneable(this)
    End Function
End Module
